package cn.edu.ecust.seckill.controller;

import cn.edu.ecust.seckill.entity.Order;
import cn.edu.ecust.seckill.entity.Product;
import cn.edu.ecust.seckill.result.Result;
import cn.edu.ecust.seckill.util.JwtUtil;
import io.jsonwebtoken.Claims;
import jakarta.servlet.http.HttpServletRequest;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RestController;

import java.time.LocalDateTime;

@RestController
public class SeckillController {

    @Autowired
    private RedisTemplate<String,Object> redisTemplate;

    /**
     * 秒杀抢单
     * 必须登录 必须没参与过 必须有库存
     */
    @PostMapping("/seckill/{productId}/order")
    public Result<Void> seckill(@PathVariable Long productId, HttpServletRequest request) {

        // 认证
        String token = request.getHeader("token");
        Claims claims = JwtUtil.parserToken(token);
        if(claims == null){
            return Result.fail(401, "请先登录");
        }
        Long userId = claims.get("id", Long.class);

        // 没有参与过该商品的秒杀
        Boolean flag = redisTemplate.opsForValue().setIfAbsent("seckill:" + productId + ":user:" + userId, 1);
        if(!flag) {
            return Result.fail(401, "您已参与过该次秒杀，请耐心等待结果");
        }

        // 有库存
        Long decrement = redisTemplate.opsForValue().decrement("seckill:" + productId + ":inventory");
        if(decrement < 0) {
            return Result.fail(401, "该商品已被抢购完，再接再厉吧");
        }

        // 创建订单
        Product product = (Product) redisTemplate.opsForValue().get("product:" + productId);
        Order order = new Order();
        order.setState(1);
        order.setTime(LocalDateTime.now());
        order.setUserId(userId);
        order.setProductId(productId);
        order.setProductTitle(product.getTitle());
        order.setProductPrice(product.getPrice());
        order.setProductImg(product.getImg());
        redisTemplate.opsForList().rightPush("list:seckill:" + productId + ":order", order);
        redisTemplate.opsForSet().add("set:seckill:" + product.getId() + ":user", userId);
        return Result.success();
    }

}
